Opscodeのaws cookbookを使ってchefからEBSの操作を行う
こんにちは。望月です。
最近はChefとPackerを使って色々な自動化に取り組んでいます。今日はOpscodeのAWS cookbookを利用してみたので、その内容をまとめてみます。
目的
起動済みのAmazon Linuxに対して、chefを適用してEBSの新規作成とmkfs、マウントを実施したいと考えました。起動する際はルートボリュームだけがアタッチされているが、cookbookを適用することにより、EBSをアタッチしてディスクが利用可能な状態に持っていこうとしました。
OpscodeのAWS cookbookではEBSやELB、EIPなどを操作するためのLWRP(LightWeight Resource and Provider)を提供しているので、cookbook内でResourceとして、EBSの操作を記述できるようになります。 *1
実行
手元の環境はMac OS X 10.9で、knife soloとBerkshelfはインストール済ということを前提とします。Chefの環境整備に関しては、次のエントリを参考にしてみてください。 AWS EC2サーバに対するknife solo実行環境構築手順 on Mac OS Xを一から整理してみる
まずはknife soloのディレクトリを作成します。
$ knife solo init chef-ebs/ WARNING: No knife configuration file found Creating kitchen... Creating knife.rb in kitchen... Creating cupboards... Setting up Berkshelf... $ cd chef-ebs $
次に、Berkshelfを使ってOpscodeのEC2 cookbookをダウンロードしてきます。
$ vi Berksfile $ cat Berksfile source 'https://api.berkshelf.com' cookbook "aws" $ berks install Resolving cookbook dependencies... Fetching cookbook index from https://api.berkshelf.com... Using aws <0 class="9 0"></0>
では、新しく自前のcookbookを作成します。新規作成したcookbookからaws cookbookを利用するので、依存しているということをcookbook内のmetadata.rbに記述する必要があります。
# site-cookbooks/ 以下に、cookbookの雛形を作成 $ knife cookbook create attach-ebs -o site-cookbooks/ ** Creating cookbook attach-ebs ** Creating README for cookbook: attach-ebs ** Creating CHANGELOG for cookbook: attach-ebs ** Creating metadata for cookbook: attach-ebs $ ls site-cookbooks/ attach-ebs/ # cookbook内のmetadata.rbを編集し、一行追加 $ vi site-cookbooks/attach-ebs/metadata.rb depends "aws"
それでは、いよいよrecipeの記述です。site-cookbooks/attach-ebs/recipes/default.rbを編集します。
device_id = "/dev/sdf" mount_point = "/data" aws_ebs_volume "data volume" do action [:create, :attach] availability_zone "ap-northeast-1a" device device_id volume_type "standard" size 10 end directory mount_point do action :create mode 000755 end execute 'mkfs' do command "mkfs -t ext4 #{device_id}" # only if it's not mounted already not_if "grep -qs #{mount_point} /proc/mounts" end mount node.attach_ebs.mount_point do device device_id fstype "ext4" options %w(noatime defaults) action [:enable, :mount] end
ポイントは4行目です。aws_ebs_volumeリソースの部分が、EBS作成に関わる部分になってきます。
リソース名についてですが、レシピに記述するリソース名の規則は[パッケージ名]_[リソース名]となるようです。今回の場合、awsクックブックのebs_volumeリソースを利用するので、aws_ebs_volumeという名前を使用します。以上、余談でした。
このレシピでは、EBSを作成した後、ファイルシステムの作成とマウントまで実行します。ただし、本番に適用するなら、mkfsの部分はもうちょっと冪等性を保証した書き方にしないといけませんね。
それでは、実際に適用してみましょう。EBSを作成するProviderは、内部的にright_awsというRuby gemを利用しています。そのgemをインストールするために、EC2 cookbookのrecipeを先に適用しましょう。
$ knife solo prepare ec2-user@ec2-xx-xx-xx-xx.ap-northeast-1.compute.amazonaws.com $ knife solo cook ec2-user@ec2-xx-xx-xx-xx.ap-northeast-1.compute.amazonaws.com -o "recipe[aws],recipe[detach-ebs]" <...snip...> Starting Chef Client, version 11.12.2 [2014-05-23T08:47:41+00:00] WARN: Run List override has been provided. [2014-05-23T08:47:41+00:00] WARN: Original Run List: [] [2014-05-23T08:47:41+00:00] WARN: Overridden Run List: [recipe[aws], recipe[attach-ebs]] Compiling Cookbooks... Recipe: aws::default * chef_gem[right_aws] action install Converging 5 resources * chef_gem[right_aws] action install Recipe: attach-ebs::default * aws_ebs_volume[data volume] action create - create a volume with id= size=10 availability_zone=ap-northeast-1a and update the node data with created volume's id * aws_ebs_volume[data volume] action attach - attach the volume with aws_id=vol-ebc363e1 id=i-c45216c2 device=/dev/sdf and update the node data with created volume's id * directory[/data] action create (up to date) * execute[mkfs] action run - execute mkfs -t ext4 /dev/sdf * mount[/data] action enable - remount /dev/sdf * mount[/data] action mount - mount /dev/sdf to /data Running handlers: Running handlers complete Chef Client finished, 5/8 resources updated in 23.848966494 seconds
新規にEBSが作成され、マウントがされていることが確認できます。ChefからAWSのリソースが扱えると、インスタンスのセットアップが非常に簡単になりますね。
また、EBSのdetachやスナップショットの作成も、以下の様にレシピに記述することができます。感覚はEBSをcreateする時と同じですね。サンプルレシピは以下のようなものです。
aws_ebs_volume "detach_volume" do action :detach device device_id # デバイスIDを指定して、そのEBSをdetachする(事前にumountしておきましょう) end aws_ebs_volume "take_snapshot" do action :detach device device_id # デバイスIDを指定して、そのデバイスIDのEBSをスナップショット作成する end
まとめ
Opscodeのaws cookbookを利用して、EBSを新規に作成する方法についてご紹介しました。aws cookbookでは、EBSの他にもEIPやELBなども操作することができるようです。これについては別のエントリでご紹介しようと思います。
参考資料
脚注
- LWRPについては、こちらのサイトが非常に参考になります。 : [LWRPによる]続・ChefでSourceから何かをインストールするCookbookのウォークスルー ↩